package com.slz.crm.server.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.slz.crm.common.exiception.BaseException;
import com.slz.crm.common.untils.BaseUnit;
import com.slz.crm.common.untils.ForeignKeyDeleteUtil;
import com.slz.crm.pojo.dto.ContractDTO;
import com.slz.crm.pojo.entity.ContractEntity;
import com.slz.crm.pojo.entity.CustomerCompanyEntity;
import com.slz.crm.pojo.entity.SalesOpportunityEntity;
import com.slz.crm.pojo.vo.ContractANDOrderVO;
import com.slz.crm.pojo.vo.ContractVO;
import com.slz.crm.pojo.vo.OrderVO;
import com.slz.crm.server.annotation.Privacy;
import com.slz.crm.server.constant.MessageConstant;
import com.slz.crm.server.mapper.ContractMapper;
import com.slz.crm.server.mapper.CustomerCompanyMapper;
import com.slz.crm.server.mapper.SalesOpportunityMapper;
import com.slz.crm.server.service.ContractOrderItemService;
import com.slz.crm.server.service.ContractService;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.ArrayList;
import java.util.List;
import java.util.UUID;

@Service
@Slf4j
public class ContractServiceImpl extends ServiceImpl<ContractMapper, ContractEntity> implements ContractService {

    @Autowired
    private SalesOpportunityMapper salesOpportunityMapper;
    @Autowired
    private ForeignKeyDeleteUtil foreignKeyDeleteUtil;
    @Autowired
    private ContractMapper contractMapper;
    @Autowired
    private ContractOrderItemService contractOrderItemService;
    @Autowired
    private CustomerCompanyMapper customerCompanyMapper;

    /**
     * 获取合同相关的公司名称和商机名称
     *
     * @param entity 合同实体
     * @return 包含公司名称和商机名称的数组，顺序为：[companyName, opportunityName]
     */
    private String[] getContractNames(ContractEntity entity) {
        String companyName = null;
        String opportunityName = null;

        // 公司名称
        if (entity.getCompanyId() != null) {
            CustomerCompanyEntity companyEntity = customerCompanyMapper.selectById(entity.getCompanyId());
            if (companyEntity != null) {
                companyName = companyEntity.getCompanyName();
            }
        }

        // 商机名称
        if (entity.getOpportunityId() != null) {
            SalesOpportunityEntity salesOpportunityEntity = salesOpportunityMapper.selectById(entity.getOpportunityId());
            if (salesOpportunityEntity != null) {
                opportunityName = salesOpportunityEntity.getOpportunityName();
            }
        }

        return new String[]{companyName, opportunityName};
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public ContractVO create(ContractDTO dto) {

        ContractEntity entity = new ContractEntity();
        BeanUtils.copyProperties(dto, entity);
        Long currentId = BaseUnit.getCurrentId();
        entity.setCreatorId(currentId);

        if (entity.getContractStatus() == null) {
            entity.setContractStatus(0);
        }

        if (entity.getContractNo() == null) {
            entity.setContractNo(UUID.randomUUID().toString());
        }

        //如果没有公司客户id，就根据商机ID查询公司客户id
        if (entity.getCompanyId() == null) {
            SalesOpportunityEntity salesOpportunityEntity = salesOpportunityMapper.selectOne(new LambdaQueryWrapper<SalesOpportunityEntity>().eq(SalesOpportunityEntity::getId, entity.getOpportunityId()));
            if (salesOpportunityEntity == null) {
                throw new RuntimeException(MessageConstant.OPPORTUNITY_IS_NOT_EXIST);
            }
            entity.setCompanyId(salesOpportunityEntity.getCompanyId());
        }

        save(entity);
        String[] names = getContractNames(entity);

        return ContractVO.fromEntity(entity, names[0], names[1]);
    }

    @Override
    @Privacy
    public ContractANDOrderVO getDetailById(Long id) {
        // 参数校验
        if (id == null) {
            throw new BaseException(MessageConstant.PARAM_ERROR);
        }

        // 1. 获取合同基本信息
        ContractVO contractVO = this.getContractById(id);

        // 2. 获取关联订单信息
        List<OrderVO> ordersVO = contractOrderItemService.getOrderListByContractId(id);

        // 3. 组装返回结果
        ContractANDOrderVO vo = new ContractANDOrderVO();
        vo.setContract(contractVO);
        vo.setOrders(ordersVO);

        return vo;
    }

    @Override
    public ContractVO getContractById(Long id) {
        ContractEntity entity = getById(id);
        if (entity == null) {
            throw new BaseException(MessageConstant.CONTRACT_IS_NOT_EXIST);
        }

        String[] names = getContractNames(entity);
        return ContractVO.fromEntity(entity, names[0], names[1]);
    }

    @Override
    @Privacy
    public Page<ContractVO> contractQuery(Integer pageNum, Integer pageSize, ContractDTO dto) {
        Page<ContractEntity> page = new Page<>(pageNum, pageSize);

        LambdaQueryWrapper<ContractEntity> queryWrapper = new LambdaQueryWrapper<>();
        // 自定义查询条件
        if (dto != null) {
            if (dto.getContractName() != null && !dto.getContractName().isEmpty()) {
                queryWrapper.like(ContractEntity::getContractName, dto.getContractName());
            }
            if (dto.getContractNo() != null && !dto.getContractNo().isEmpty()) {
                queryWrapper.eq(ContractEntity::getContractNo, dto.getContractNo());
            }
            if (dto.getCompanyId() != null) {
                queryWrapper.eq(ContractEntity::getCompanyId, dto.getCompanyId());
            }
            if (dto.getContractStatus() != null) {
                queryWrapper.eq(ContractEntity::getContractStatus, dto.getContractStatus());
            }
            if (dto.getOwnerId() != null) {
                queryWrapper.eq(ContractEntity::getOwnerId, dto.getOwnerId());
            }
        }

        // 默认按创建时间倒序
        queryWrapper.orderByDesc(ContractEntity::getCreateTime);

        Page<ContractEntity> entityPage = page(page, queryWrapper);

        // 转换为VO
        Page<ContractVO> voPage = new Page<>();
        BeanUtils.copyProperties(entityPage, voPage);

        List<ContractVO> voList = entityPage.getRecords().stream()
                .map(entity -> {
                    String[] names = getContractNames(entity);
                    return ContractVO.fromEntity(entity, names[0], names[1]);
                })
                .toList();

        voPage.setRecords(voList);
        return voPage;
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public boolean update(ContractDTO dto) {
        if (dto.getId() == null) {
            throw new RuntimeException(MessageConstant.ID_IS_NULL);
        }

        ContractEntity entity = getById(dto.getId());
        if (entity == null) {
            throw new RuntimeException(MessageConstant.CONTRACT_IS_NOT_EXIST);
        }

        BeanUtils.copyProperties(dto, entity);
//        entity.setUpdateTime(BaseUnit.getCurrentTime());

        return updateById(entity);
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public int batchDelete(List<Long> ids) {
        if (ids == null || ids.isEmpty()) {
            throw new RuntimeException(MessageConstant.ID_LIST_IS_NULL);
        }

        // 收集不符合状态的合同ID
        List<String> invalidIds = new ArrayList<>();
        List<ContractEntity> entities = listByIds(ids);
        for (ContractEntity entity : entities) {
            if (entity.getContractStatus() != 4) {
                invalidIds.add(entity.getId().toString());
            }
        }

        // 有不符合的，抛拼接后的提示
        if (!invalidIds.isEmpty()) {
            String msg = MessageConstant.CONTRACT_NOT_IN_DISCARD_STATUS
                    + "，不符合的合同ID：" + String.join(",", invalidIds);
            throw new RuntimeException(msg);
        }

        foreignKeyDeleteUtil.deleteCascade(ContractEntity.class, ids, 0);
        return contractMapper.deleteBatchIds(ids);
    }

    @Override
    public Page<ContractVO> getAllContract(Integer pageNum, Integer pageSize) {

        Page<ContractEntity> page = new Page<>(pageNum, pageSize);
        Page<ContractEntity> pageResult = contractMapper.selectPage(
                page,
                new LambdaQueryWrapper<ContractEntity>()
                        .orderByDesc(ContractEntity::getCreateTime)
        );

        List<ContractVO> contractVOs = pageResult.getRecords().stream()
                .map(entity -> {
                    String[] names = getContractNames(entity);
                    return ContractVO.fromEntity(entity, names[0], names[1]);
                })
                .toList();

        Page<ContractVO> pageVO = new Page<>(pageNum, pageSize, pageResult.getTotal());
        BeanUtils.copyProperties(pageResult, pageVO);
        pageVO.setRecords(contractVOs);
        return pageVO;
    }
}
